/**
 * 账号
 * 验证规则：字母、数字或下划线组成，字母开头，4-16位。
 */
export const accountRule = [
    {pattern: /^[a-zA-z](\w?){4,30}$/, message: '请输入以字母开头的4-30位字母、数字或下划线的组合'},
    {min: 4, max: 30, message: '长度在 4 到 30 个字符'},
]

/**
 * 密码
 * 验证规则：待定。
 */
export const passwordRule = [
    {pattern: /^(?=.*[a-zA-Z])(?=.*\d).{6,20}$/, message: '密码由6-20位数字、字母或两种符号以上的组合'},
    {min: 6, max: 20, message: '长度在 6 到 20 个字符'},
]

/**
 * 邮箱
 * 验证规则：待定。
 */
export function emailRule (rule, value, callback) {
    const pattern = /^([a-zA-Z0-9_-])+@([a-zA-Z0-9_-])+((.[a-zA-Z0-9_-]{2,3}){1,2})$/;
    if (value != '' && !pattern.test(value)) {
        callback(new Error('请输入有效的邮箱'))
    } else {
        callback()
    }
}

/**
 * 判断是否为整数
 * @param s
 * @returns {boolean}
 */
export function isInteger(rule,value,callback) {
    const pattern = /^[0-9]*[1-9][0-9]*$/;
    if(value != '' && !pattern.test(value)){
        callback(new Error('请输入有效的数据'))
    } else {
        callback();
    }
}

/**
 * 判断是否为空
 */
export function validatenull(val) {
    if (typeof val == 'boolean') {
        return false;
    }
    if (typeof val == 'number') {
        return false;
    }
    if (val instanceof Array) {
        if (val.length == 0) return true;
    } else if (val instanceof Object) {
        if (JSON.stringify(val) === '{}') return true;
    } else {
        if (val == 'null' || val == null || val == 'undefined' || val == undefined || val == '') return true;
        return false;
    }
    return false;
}

/**
 * URL地址
 * @param {*} s
 */
export function isURL(s) {
    return /^http[s]?:\/\/.*/.test(s)
}

/**
 *
 * @param rule
 * @param value
 * @param callback
 */
export function urlRule (rule, value, callback) {
  let mvalue = value;
  let pattern = /^http[s]?:\/\/.*/;
  if (mvalue != '' && !pattern.test(mvalue)) {
    callback(new Error('请输入有效的URL地址'))
  } else{
    callback()
  }
}

/**
 * 判断手机号码是否正确
 */
export function validateMobile(mobile) {
    let mvalue = mobile;
    //移动号段
    let pattern1 = /^0{0,1}(13[4-9]|14[37]|15[012789]|18[23478]|17[028]|198)[0-9]{8}$/;
    //联通号段
    let pattern2 = /^0{0,1}(13[0-2]|14[56]|15[56]|166|17[156]|18[56])[0-9]{8}$/;
    //电信号段
    let pattern3 = /^0{0,1}(133|141|153|17[0347]|18[019]|19[19])[0-9]{8}$/;
    if (mvalue != '' && !pattern1.test(mvalue) && !pattern2.test(mvalue) && !pattern3.test(mvalue)) {
        return false;
    } else {
        return true;
    }
}

//严格校验模式，按照运营商已有号段校验（存在变化）
export function mobileRule (rule, value, callback) {
    let mvalue = value;
    //移动号段
    let pattern1 = /^0{0,1}(13[4-9]|14[37]|15[012789]|18[23478]|17[028]|198)[0-9]{8}$/;
    //联通号段
    let pattern2 = /^0{0,1}(13[0-2]|14[56]|15[56]|166|17[156]|18[56])[0-9]{8}$/;
    //电信号段
    let pattern3 = /^0{0,1}(133|141|153|17[0347]|18[019]|19[19])[0-9]{8}$/;
    if (mvalue != '' && !pattern1.test(mvalue) && !pattern2.test(mvalue) && !pattern3.test(mvalue)) {
        callback(new Error('请输入有效的手机号码'))
    } else{
        callback()
    }
}

/**
 * 身份证号校验
 * @param rule
 * @param value
 * @param callback
 */
export function idCardRule(rule, value, callback) {
    let idCard = value;
    const Wi = [ 7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2, 1 ];// 加权因子
    const ValideCode = [ 1, 0, 10, 9, 8, 7, 6, 5, 4, 3, 2 ];// 身份证验证位值.10代表X
    const isTrueValidateCodeBy18IdCard = function(idCard) {
        let sum = 0; // 声明加权求和变量
        let a_idCard=idCard.split("");
        if (a_idCard[17].toLowerCase() == 'x') {
            a_idCard[17] = 10;// 将最后位为x的验证码替换为10方便后续操作
        }
        for ( let i = 0; i < 17; i++) {
            sum += Wi[i] * a_idCard[i];// 加权求和
        }
        if (a_idCard[17] == ValideCode[sum % 11]) {
            return true;
        } else {
            return false;
        }
    };
    const isValidityBrithBy18IdCard = function(idCard18){
        let year =  idCard18.substring(6,10);
        let month = idCard18.substring(10,12);
        let day = idCard18.substring(12,14);
        let temp_date = new Date(year,parseFloat(month)-1,parseFloat(day));
        // 这里用getFullYear()获取年份，避免千年虫问题
        if (temp_date.getFullYear()!=parseFloat(year)
            ||temp_date.getMonth()!=parseFloat(month)-1
            ||temp_date.getDate()!=parseFloat(day)) {
            return false;
        } else {
            temp_date = year+"-"+month+"-"+day;
            return true;
        }
    };
    const isValidityBrithBy15IdCard = function(idCard15){
        let year =  idCard15.substring(6,8);
        let month = idCard15.substring(8,10);
        let day = idCard15.substring(10,12);
        let temp_date = new Date(year,parseFloat(month)-1,parseFloat(day));
        // 对于老身份证中的你年龄则不需考虑千年虫问题而使用getYear()方法
        if (temp_date.getYear()!=parseFloat(year)
            ||temp_date.getMonth()!=parseFloat(month)-1
            ||temp_date.getDate()!=parseFloat(day)) {
            return false;
        } else {
            return true;
        }
    };
    if (idCard) {
        if (/^(\d{15}$|^\d{18}$|^\d{17}(\d|X|x))$/.test(idCard)) {
            if (idCard.length == 15 && isValidityBrithBy15IdCard(idCard)) {
                callback()
            } else if (idCard.length == 18 && isValidityBrithBy18IdCard(idCard) && isTrueValidateCodeBy18IdCard(idCard)){
                callback()
            } else {
                callback(new Error('请输入有效的身份证号'))
            }
        } else {
            callback(new Error('请输入有效的身份证号'))
        }
    } else {
        callback()
    }
}

/**
 * 统一社会信用代码校验
 * @param rule
 * @param value
 * @param callback
 */
export function socialCodeRule(rule, value, callback) {
  let cardno = value;
  const patrn = /^[0-9A-Z]+$/;
  if (cardno) {
    if ((cardno.length != 18) || (patrn.test(cardno) == false)) {
      callback(new Error('请输入有效的统一社会信用代码'))
    } else {
      let Ancode;//统一社会信用代码的每一个值
      let Ancodevalue;//统一社会信用代码每一个值的权重
      let total = 0;
      let weightedfactors = [1, 3, 9, 27, 19, 26, 16, 17, 20, 29, 25, 13, 8, 24, 10, 30, 28];//加权因子
      let str = '0123456789ABCDEFGHJKLMNPQRTUWXY';
      //不用I、O、S、V、Z
      for (let i = 0; i < cardno.length - 1; i++) {
        Ancode = cardno.substring(i, i + 1);
        Ancodevalue = str.indexOf(Ancode);
        total = total + Ancodevalue * weightedfactors[i];
        //权重与加权因子相乘之和
      }
      let logiccheckcode = 31 - total % 31;
      if (logiccheckcode == 31) {
        logiccheckcode = 0;
      }
      let Str = "0,1,2,3,4,5,6,7,8,9,A,B,C,D,E,F,G,H,J,K,L,M,N,P,Q,R,T,U,W,X,Y";
      let Array_Str = Str.split(',');
      logiccheckcode = Array_Str[logiccheckcode];
      let checkcode = cardno.substring(17, 18);
      if (logiccheckcode != checkcode) {
        callback(new Error('请输入有效的统一社会信用代码'))
      } else {
        callback()
      }
    }
  } else {
    callback()
  }
}
